package com.sftz.modules.minapp.pay.service;

import java.util.Map;
import java.util.TreeMap;

import org.nutz.ioc.loader.annotation.IocBean;
import org.nutz.log.Log;
import org.nutz.log.Logs;

import com.sftz.framework.ioc.CustomIocProvider;
import com.sftz.framework.rersult.MobileResult;
import com.sftz.framework.vendors.minapp.WeappServiceConfig;
import com.sftz.modules.minapp.pay.dto.WeixinUnifiedOrderParam;
import com.sftz.modules.minapp.pay.enums.WeixinPayChannelEnum;
import com.sftz.modules.minapp.pay.form.WxMpPayOrderForm;
import com.sftz.modules.minapp.pay.util.HttpRequest;
import com.tencent.common.RandomStringGenerator;
import com.tencent.common.Signature;
import com.tencent.common.XMLParser;
import com.uxuexi.core.common.util.EnumUtil;
import com.uxuexi.core.common.util.MapUtil;
import com.uxuexi.core.common.util.Util;

@IocBean
public class WxMpPayService {

	private static final Log log = Logs.get();

	//交易类型
	private static final String JSAPI_TRADE_TYPE = "JSAPI";//公众号支付

	private WeappServiceConfig conf = CustomIocProvider.getBean("weappServiceConfig", WeappServiceConfig.class);

	public Map<String, Object> prepay(WxMpPayOrderForm form) {
		String notify_url = conf.getNotifyUrl();
		return prepay(form, notify_url, WeixinPayChannelEnum.MP.intKey());
	}

	private Map<String, Object> prepay(WxMpPayOrderForm order, final String notify_url, final int pay_way) {
		WeixinUnifiedOrderParam wxOrderParam = new WeixinUnifiedOrderParam();
		//调用微信统一下单(预支付)
		wxOrderParam.setAppId(conf.getAppid());
		wxOrderParam.setAmount(order.getAmount());
		wxOrderParam.setBody(order.getGoodsName());
		wxOrderParam.setOrderNo(order.getOrderNo());
		wxOrderParam.setCreateTime(order.getCreateTime());

		String signKey = "";
		String trade_type = "";
		if (!Util.isEmpty(order)) {
			WeixinPayChannelEnum weixinPayChannel = EnumUtil.get(WeixinPayChannelEnum.class, pay_way);
			switch (weixinPayChannel) {
			case APP:
				//trade_type  TODO
				log.info("微信APP支付,统一下单");
				break;
			case MP:
				log.info("微信公众号支付,统一下单");
				signKey = conf.getMchKey();
				trade_type = JSAPI_TRADE_TYPE;
				break;
			case ACNATIVE:
				log.info("公众号扫码支付,统一下单");
				break;
			default:
				log.info("未知的微信支付类型");
				throw new IllegalArgumentException("未知的微信支付类型");
			}

			String body = order.getGoodsName();

			Map<String, Object> params = new TreeMap<String, Object>();
			params.put("appid", conf.getAppid());
			params.put("mch_id", conf.getMchId());
			params.put("notify_url", notify_url);
			params.put("trade_type", trade_type);//交易类型
			params.put("nonce_str", RandomStringGenerator.getRandomStringByLength(32));

			//trade_type=JSAPI时（即公众号支付），此参数必传
			if (JSAPI_TRADE_TYPE.equals(trade_type)) {
				params.put("openid", order.getOpenid());
			}
			params.put("body", body);
			String out_trade_no = order.getOrderNo();
			params.put("out_trade_no", order.getOrderNo());

			long total_fee = order.getAmount();
			params.put("total_fee", total_fee);
			params.put("device_info", "WEB");//自定义参数(可选)，可以为终端设备号(门店号或收银设备ID)，PC网页或公众号内支付可以传"WEB"

			String sign = Signature.getSign(params, signKey);
			params.put("sign", sign);

			//统一下单,预支付
			String result = HttpRequest.sendPost(conf.getUnifiedUrl(), params);
			log.info("weixin_prepay:" + result);
			Map<String, Object> weixinPrepayInfo = MapUtil.map();
			try {
				weixinPrepayInfo = XMLParser.getMapFromXML(result);

				String return_code = (String) weixinPrepayInfo.get("return_code");
				if ("SUCCESS".equals(return_code)) {
					String result_code = (String) weixinPrepayInfo.get("result_code");
					if ("SUCCESS".equals(result_code)) {
						weixinPrepayInfo.put("key", signKey);
						//异步通知地址
						weixinPrepayInfo.put("notify_url", notify_url);
						weixinPrepayInfo.put("total_fee", total_fee);
						weixinPrepayInfo.put("out_trade_no", out_trade_no);

						String prepay_id = (String) weixinPrepayInfo.get("prepay_id");
						String code_url = (String) weixinPrepayInfo.get("code_url");
						wxOrderParam.setCode_url(code_url);//二维码支付链接（native支付会提供）
						wxOrderParam.setPrepay_id(prepay_id);
						wxOrderParam.setPackageInfo("prepay_id=" + prepay_id);
						wxOrderParam.setPaySign(getParamSign(wxOrderParam, signKey));

						return MobileResult.success("提交成功", wxOrderParam);
					} else {
						String err_code_des = (String) weixinPrepayInfo.get("err_code_des");
						return MobileResult.error(err_code_des, null);
					}
				} else {
					String return_msg = (String) weixinPrepayInfo.get("return_msg");
					return MobileResult.error(return_msg, null);
				}
			} catch (Exception e) {
				return MobileResult.error("调用微信预支付接口出错.", null);
			}
		}//end of order if
		else {
			return MobileResult.error("订单信息不能为空", null);
		}
	}

	/**获取参数签名*/
	private String getParamSign(WeixinUnifiedOrderParam param, String signKey) {
		Map<String, Object> params = new TreeMap<String, Object>();
		params.put("appId", conf.getAppid());
		params.put("timeStamp", param.getTimeStamp());
		params.put("nonceStr", param.getNonceStr());
		params.put("package", param.getPackageInfo());
		params.put("signType", param.getSignType());
		return Signature.getSign(params, signKey);
	}

}
